import * as Cesium from 'cesium';
import {calcAngle, uuid} from "../../utils/index";
// const Cesium = window.Cesium
//天地图key
const key = 'd786b5f312e2a5dee39b667a5805263c'

// 初始视图定位在中国
Cesium.Camera.DEFAULT_VIEW_RECTANGLE = Cesium.Rectangle.fromDegrees(90, -20, 110, 90);
const themeColor = new Cesium.Color(0.878, 0.38, 0.05)
const dockColor = new Cesium.Color(0.145, 0.635, 0.988)
let viewer = null;
let entitiesCacheObj = {}
function initMap(container) {
    viewer = new Cesium.Viewer(container, {
        // imageryProvider:false,  //关闭默认的imageryProvider
        animation: false,
        baseLayerPicker: false,
        fullscreenButton: false,
        geocoder: false,
        homeButton: false,
        infoBox: false,
        sceneModePicker: false,
        selectionIndicator: false,
        timeline: false,
        navigationHelpButton: false,
        scene3DOnly: true,
        orderIndependentTranslucency: false,
        contextOptions: {
            webgl: {
                alpha: true
            }
        },
    })
    viewer._cesiumWidget._creditContainer.style.display = 'none'
    viewer.scene.fxaa = true
    viewer.scene.globe.enableRoll = true
    if (Cesium.FeatureDetection.supportsImageRenderingPixelated()) {
        viewer.resolutionScale = window.devicePixelRatio
    }
    // 移除默认影像
    removeAll()
    viewer.scene.postProcessStages.fxaa.enabled = true;
    // 地形深度测试
    viewer.scene.globe.depthTestAgainstTerrain = true
    // 背景透明
    viewer.scene.globe.baseColor = new Cesium.Color(0.0, 0.0, 0.0, 0)
    // 设置鼠标右键旋转相机视角
    viewer.scene.screenSpaceCameraController.tiltEventTypes = [Cesium.CameraEventType.PINCH, Cesium.CameraEventType.RIGHT_DRAG];
    const handler = new Cesium.ScreenSpaceEventHandler(viewer.scene.canvas);
    handler.setInputAction(function (movement) {
        // console.log(movement)
        var pick = viewer.scene.pick(movement.position);
        console.log('*****************', pick);

    },Cesium.ScreenSpaceEventType.LEFT_CLICK);

}
function addGlb(options) {
    let customShader = new Cesium.CustomShader({
        //片元着色器
        fragmentShaderText: `
        void fragmentMain(FragmentInput fsInput, inout czm_modelMaterial material) {
            // vec3 positionMC = fsInput.attributes.code;


        }`
    })
    const modelMatrix = Cesium.Transforms.eastNorthUpToFixedFrame(
        Cesium.Cartesian3.fromDegrees(options.longitude, options.latitude, options.height)
    );
    Cesium.Model.fromGltfAsync({
        id: '111222',
        modelMatrix,
        url: options.url,
        scale: 1,
        minimumPixelSize: 128,
        maximumScale: 20000,
        enablePick: true,
        allowPicking: true,
    }).then((model) => {
        // model.customShader = customShader
        // console.log(model._nodesByName)
        console.log(model)
        const m = viewer.scene.primitives.add(model);
    })
}
function addGlb3(options) {
    const modelMatrix = Cesium.Transforms.eastNorthUpToFixedFrame(
        Cesium.Cartesian3.fromDegrees(options.longitude, options.latitude, options.height)
    );
    const model = viewer.scene.primitives.add(Cesium.Model.fromGltf({
        id: '111222',
        modelMatrix,
        url: options.url,
        scale: 1,
        minimumPixelSize: 128,
        maximumScale: 20000,
        enablePick: true,
        allowPicking: true,
    }))
    console.log(model)
    // model.readyPromise.then((a, b, c) => {
    //     console.log(a,b,c)
    // })

}
function addGlb2(options) {
    const entity = viewer.entities.add({
        name : options.name,
        description:"<div><p>这是一个飞机！</div>", // 这是模型的描述属性，可以是html标签
        position : options.position,
        orientation : options.orientation,
        model : {
            uri : options.uri,
            minimumPixelSize : 128,
            maximumScale : 20000
        }
    });
}
function addEntity(entity) {
    return viewer.entities.add(entity);
}
function drawOutlinePoint(sn, pos, pixelSize) {
    const pointEntity = addEntity({
        id: uuid(12),
        position: Cesium.Cartesian3.fromDegrees(pos[0],pos[1],pos[2]),
        point: {
            pixelSize,// 点大小
            color: themeColor.withAlpha(0.1),// 点颜色
            outlineColor: Cesium.Color.WHITE.withAlpha(0.1), // 边框颜色
            outlineWidth: 2, // 边框宽度
        },
    })
    entitiesCacheObj[sn].pointEntities.push(pointEntity)
    return pointEntity
}
function drawLine(sn, pos1, pos2) {
    if (!pos1 || !pos2) {
        return
    }
    const positions = [
        Cesium.Cartesian3.fromDegrees(pos1[0],pos1[1],pos1[2]),
        Cesium.Cartesian3.fromDegrees(pos2[0],pos2[1],pos2[2]),
    ];
    const lineEntity = addEntity({
        id: uuid(12),
        polyline: {
            positions: positions,          // 线的位置数组
            width: 2,                      // 线宽
            material: themeColor    // 线的颜色
        }
    });
    entitiesCacheObj[sn].lineEntities.push(lineEntity)
    return lineEntity
}
function drawAircraf(sn, pos) {
    const position = Cesium.Cartesian3.fromDegrees(pos[0],pos[1],pos[2])
    if (!entitiesCacheObj[sn]) {
        entitiesCacheObj[sn] = {
            entity: new Cesium.Entity({
                id: sn,
                position,
                orientation: Cesium.Transforms.headingPitchRollQuaternion(position, {
                    heading: 0,
                    pitch:0,
                    roll: 0
                }),
                billboard: {
                    image: '/feiji.png',
                    scale: 0.3,
                    rotation: Cesium.Math.toRadians(0.0),
                }
            }),
            pointEntities: [],//缓存点实体
            lineEntities: [],//缓存线段实体
            prevPos: null
        }
        addEntity(entitiesCacheObj[sn].entity)
    } else {
        entitiesCacheObj[sn].entity.position = position
    }
    if (entitiesCacheObj[sn].prevPos) {
        const ang = calcAngle(entitiesCacheObj[sn].prevPos, pos)
        entitiesCacheObj[sn].entity.billboard.rotation = Cesium.Math.toRadians(ang)
    }
}
function drawDock(sn, title, pos) {
    const position = Cesium.Cartesian3.fromDegrees(pos[0],pos[1],pos[2])
    const labelEntity = addEntity({
        id: sn + '_label',
        position,
        label: {
            text: title,
            font: '28px Helvetica',
            scale: 0.5,
            showBackground: true,
            backgroundColor: dockColor,
            backgroundPadding: new Cesium.Cartesian2(10, 10),
            fillColor: Cesium.Color.WHITE,
            // outlineColor: Cesium.Color.BLACK,
            // outlineWidth: 1,
            style: Cesium.LabelStyle.FILL,
            verticalOrigin: Cesium.VerticalOrigin.BOTTOM,
            pixelOffset: new Cesium.Cartesian2(0, -30),
        }
    });
    const bgEntity = addEntity({
        id: sn + '_bg',
        position,
        point: {
            pixelSize: 60,// 点大小
            color: dockColor,// 点颜色
        },
    });
    entitiesCacheObj[sn] = {
        entity: new Cesium.Entity({
            id: sn,
            position,
            orientation: Cesium.Transforms.headingPitchRollQuaternion(position, {
                heading: 0,
                pitch:0,
                roll: 0
            }),
            billboard: {
                image: '/drone_in_dock2.png',
                scale: 0.2,
                rotation: Cesium.Math.toRadians(0.0),
            }
        }),
        labelEntity,
        bgEntity,
        pos,
    }
    return addEntity(entitiesCacheObj[sn].entity)

}
function clearAircrafPointAndLine(sn) {
    if (!entitiesCacheObj[sn]) {
        return
    }
    const entities = entitiesCacheObj[sn].pointEntities.concat(entitiesCacheObj[sn].lineEntities)
    const size = entities.length
    for(let i=size-1; i>=0; i--){
        viewer.entities.remove(entities[i])
    }
    entitiesCacheObj[sn].pointEntities = []
    entitiesCacheObj[sn].lineEntities = []
}
function pointFadeScaleAnimation(entity, targetAlpha, targetSize, duration, delay, callback) {
    setTimeout(() => {
        const graphics = entity.point;
        let startAlpha;
        let startAlphaOutline;
        let startSize;
        startAlpha = graphics.color.getValue().alpha;
        startSize = graphics.pixelSize;
        if (graphics.outlineColor) {
            startAlphaOutline = graphics.outlineColor.getValue().alpha;
        }
        let startTime = 0;
        const animate = (currentTime) => {
            if (!startTime) {
                startTime = currentTime;
            }
            const elapsedTime = currentTime - startTime;

            if (elapsedTime < duration) {
                const deltalpha = (elapsedTime / duration) * (targetAlpha - startAlpha);
                const newAlpha = startAlpha + deltalpha;

                const deltSize = (elapsedTime / duration) * (targetSize - startSize);
                const newSize = startSize + deltSize;

                const deltalphaOutline = (elapsedTime / duration) * (targetAlpha - startAlphaOutline);
                const newAlphaOutline = startAlphaOutline + deltalphaOutline;

                const newColor = graphics.color.getValue().withAlpha(newAlpha);
                graphics.color.setValue(newColor);

                graphics.pixelSize = newSize;

                if (graphics.outlineColor) {
                    const newColorOutline = graphics.outlineColor.getValue().withAlpha(newAlphaOutline);
                    graphics.outlineColor.setValue(newColorOutline);
                }

                requestAnimationFrame(animate);
            } else {
                // Animation Ended
                callback && callback();
                const newColor = graphics.color.getValue().withAlpha(targetAlpha);
                graphics.color.setValue(newColor);
                graphics.pixelSize = targetSize
                if (graphics.outlineColor) {
                    const newColorOutline = graphics.outlineColor.getValue().withAlpha(targetAlpha);
                    graphics.outlineColor.setValue(newColorOutline);
                }
                requestAnimationFrame(() => {});
            }
        };

        requestAnimationFrame(animate);
    }, delay);
}
function addTdtLayer(options) {
    let url = `https://t{s}.tianditu.gov.cn/DataServer?T=${options.type}&x={x}&y={y}&l={z}&tk=${key}`
    const layerProvider = new Cesium.UrlTemplateImageryProvider({
        url: url,
        subdomains: ['0','1','2','3','4','5','6','7'],
        tilingScheme: new Cesium.WebMercatorTilingScheme(),
        maximumLevel: 18
    });
    viewer.imageryLayers.addImageryProvider(layerProvider);
}


function addTdtLayer2(options) {
    let url = `https://t{s}.tianditu.gov.cn/${options.type}/wmts?tk=${key}`
    const layerProvider = new Cesium.WebMapTileServiceImageryProvider({
        url: url,
        layer: options.type.slice(0,options.type.length - 2),
        style: 'default',
        format: 'tiles',
        tileMatrixSetID: "w",
        tilingScheme: new Cesium.WebMercatorTilingScheme(),
        subdomains: ['0','1','2','3','4','5','6','7'],
        maximumLevel: 18
    });
    viewer.imageryLayers.addImageryProvider(layerProvider);
}

function changeBaseMap(type) {
    removeAll()
    switch(type) {
        case 0: //影像地图
            addTdtLayer({
                type: 'img_w'
            })
            addTdtLayer({
                type: 'cia_w'
            })
            break
        case 1: //电子地图
            addTdtLayer({
                type: 'vec_w'
            })
            addTdtLayer({
                type: 'cva_w'
            })
            break
        case 2: //地形图
            addTdtLayer({
                type: 'ter_w'
            })
            addTdtLayer({
                type: 'cta_w'
            })
            break
    }
}

function removeAll() {
    viewer.imageryLayers.removeAll();
}

function destroy() {
    viewer.entities.removeAll();
    viewer.imageryLayers.removeAll();
    viewer.destroy();
}

function setView(coords,hpr) {
    viewer.scene.camera.flyTo({
        destination: Cesium.Cartesian3.fromDegrees(coords[0], coords[1], coords[2]),
        orientation: {
            heading: Cesium.Math.toRadians(hpr.heading),
            pitch: Cesium.Math.toRadians(hpr.pitch),
            roll: Cesium.Math.toRadians(hpr.roll),
        }
    });
}


export {
    viewer,
    entitiesCacheObj,
    initMap,
    addTdtLayer,
    changeBaseMap,
    setView,
    addGlb,
    addGlb2,
    addGlb3,
    addEntity,
    drawAircraf,
    drawOutlinePoint,
    drawLine,
    drawDock,
    clearAircrafPointAndLine,
    pointFadeScaleAnimation,
    removeAll,
    destroy
}

